/**
 * 记录列表类型
 * 
 * 用于表示键值对的对象列表，每个对象的键为字符串，值为任意类型
 * @template T - 记录值的类型，默认为any
 * @example
 * const records1: Records = [
 *   { key: 'name', value: '张三' },
 *   { key: 'age', value: 18 },
 * ];
 * const records2: Records<number|string> = [
 *   { key: 'name', value: '张三' },
 *   { key: 'age', value: 18 },
 * ];
 */
export type Records<T = any> = Record<string, T>[];

/**
 * 值类型(基本类型)
 * 
 * 包括字符串、数字、布尔值、空值、未定义、符号和大整数
 * @example
 * const value1: ValueTypes = 'string';
 * const value2: ValueTypes = 18;
 * const value3: ValueTypes = true;
 * const value4: ValueTypes = null;
 * const value5: ValueTypes = undefined;
 * const value6: ValueTypes = Symbol('symbol');
 * const value7: ValueTypes = 100n;
 */
export type ValueTypes = 'string' | 'number' | 'boolean' | 'null' | 'undefined' | 'symbol' | 'bigint';

/**
 * 引用数据类型（对象类型）
 * 
 * 包括对象、数组、函数、正则表达式和日期
 * @example
 * const value1: ReferenceTypes = {};
 * const value2: ReferenceTypes = [];
 * const value3: ReferenceTypes = () => {};
 * const value4: ReferenceTypes = /^$/;
 * const value5: ReferenceTypes = new Date();
 */
export type ReferenceTypes = 'object' | 'array' | 'function' | 'regexp' | 'date';

/**
 * 有效类型
 * 
 * 包括{@link ValueTypes 值类型}和{@link ReferenceTypes 引用数据类型}
 */
export type ValidTypes = ValueTypes | ReferenceTypes;

/**
 * 从枚举或对象中提取所有值的联合类型
 * 
 * @template T - 枚举或对象类型
 * @example
 * enum Colors {
 *   Red = 'red',
 *   Green = 'green',
 *   Blue = 'blue',
 * }
 * type ColorsValues = ValueOf<Colors>; // 'red' | 'green' | 'blue'
 */
export type ValueOf<T> = T[keyof T];

/**
 * 从类型中提取所有键的联合类型
 * 
 * @template T - 类型
 * @example
 * type Keys = KeyOf<{ a: number; b: string }>; // 'a' | 'b'
 */
export type KeyOf<T> = keyof T;



/**
 * 非空字符串类型
 * 这是一个品牌类型（Brand Type），用于在TypeScript类型系统中区分普通字符串和非空字符串
 * 
 * 重要说明：
 * - NonEmptyString是TypeScript的类型（编译时概念），不是运行时值
 * - 尝试在运行时访问NonEmptyString会导致编译错误，如：`console.log(typeof NonEmptyString)`
 * - 正确使用方式：通过类型断言或类型守卫进行类型转换
 * 
 * 示例：
 * ```typescript
 * // 正确：使用类型断言
 * const nonEmptyString: NonEmptyString = 'hello' as NonEmptyString;
 * console.log(typeof nonEmptyString); // 在运行时，仍然是'string'
 * 
 * // 通过类型守卫使用
 * const testValue1: unknown = 'test';
 * if (isString(testValue1, true)) {
 *   // 这里testValue1被推断为NonEmptyString类型
 *   console.log(testValue1.length); // 类型安全
 * }
 * 
 * const testValue2: unknown = '';
 * console.log(isString(testValue2, true)); // false
 * ```
 */
export type NonEmptyString = string & { __nonEmptyStringBrand: never };

/**
 * 非空数组类型
 * 这是一个品牌类型（Brand Type），用于在TypeScript类型系统中区分普通数组和非空数组
 * 
 * 重要说明：
 * - NonEmptyArray是TypeScript的类型（编译时概念），不是运行时值
 * - 尝试在运行时访问NonEmptyArray会导致编译错误
 * - 正确使用方式：通过类型断言或类型守卫进行类型转换
 * 
 * 示例：
 * ```typescript
 * // 正确：使用类型断言
 * const nonEmptyArray: NonEmptyArray = [1, 2, 3] as NonEmptyArray;
 * console.log(typeof nonEmptyArray); // 在运行时，仍然是'object'
 * 
 * // 通过类型守卫使用
 * const testValue1: unknown = [1, 2, 3];
 * if (isArray(testValue1, true)) {
 *   // 这里testValue1被推断为NonEmptyArray类型
 *   console.log(testValue1.length); // 类型安全
 *   console.log(testValue1[0]); // 可以安全地访问元素
 * }
 * 
 * const testValue2: unknown = [];
 * console.log(isArray(testValue2, true)); // false
 * ```
 */
export type NonEmptyArray = any[] & { __nonEmptyArrayBrand: never };

/**
 * 非空对象类型
 * 这是一个品牌类型（Brand Type），用于在TypeScript类型系统中区分普通对象和非空对象（有至少一个自有属性）
 * 
 * 重要说明：
 * - NonEmptyObject是TypeScript的类型（编译时概念），不是运行时值
 * - 尝试在运行时访问NonEmptyObject会导致编译错误
 * - 正确使用方式：通过类型断言或类型守卫进行类型转换
 * 
 * 示例：
 * ```typescript
 * // 正确：使用类型断言
 * const nonEmptyObj: NonEmptyObject = { key: 'value' } as NonEmptyObject;
 * console.log(typeof nonEmptyObj); // 在运行时，仍然是'object'
 * 
 * // 通过类型守卫使用
 * const testValue1: unknown = { key: 'value' };
 * if (isObject(testValue1, true)) {
 *   // 这里testValue1被推断为NonEmptyObject类型
 *   // 可以安全地访问对象属性
 * }
 * 
 * const testValue2: unknown = {};
 * console.log(isObject(testValue2, true)); // false
 * ```
 */
export type NonEmptyObject = object & { __nonEmptyObjectBrand: never };